package com.societyGames.flashForms
{
	import flash.display.DisplayObject;
	import flash.display.Sprite;

	public class DockContainer extends Sprite
	{
		private var _desiredWidth:Number;
		private var _desiredHeight:Number;
		private var _items:Vector.<DockItem> = new Vector.<DockItem>();

		public function DockContainer()
		{
		}
		
		public override function set width(value:Number):void
		{	
			if (value != this._desiredWidth)
			{
				this._desiredWidth = value;
				calculate();
			}
		}
		
		public override function set height(value:Number):void
		{
			if (value != this._desiredHeight)
			{	
				this._desiredHeight = value;
				calculate();
			}
		}
		
		public function addItem(item:DisplayObject, dockType:DockType, dockUnitType:DockUnitType, units:Number):void
		{
			if (units < 0)
			{
				throw new ArgumentError("Parameter \"units\" cannot be less than 0.");
			}
			if (dockUnitType == DockUnitType.percent && units > 1)
			{
				throw new ArgumentError("Parameter \"units\" cannot be greater than 1.0 if it is a percent.");
			}
			this._items.push(new DockItem(item, dockType, dockUnitType, units));
			calculate();
		}
		
		public function calculate():void
		{
			//Clear all children out.
			while (this.numChildren > 0)
			{
				this.removeChildAt(this.numChildren - 1);
			}
			var left:Number = 0;
			var right:Number = this._desiredWidth;
			var top:Number = 0;
			var bottom:Number = this._desiredHeight;
			//Go through the dock items
			for each (var item:DockItem in this._items)
			{
				var widthLeft:Number = right - left;
				var heightLeft:Number = bottom - top;
				//If we have any room left to actually render.
				if (widthLeft > 0 && heightLeft > 0)
				{
					var widthPixels:Number = item.dockUnitType == DockUnitType.pixel ? item.units : item.units * widthLeft;
					var heightPixels:Number = item.dockUnitType == DockUnitType.pixel ? item.units : item.units * heightLeft;
					switch (item.dockType)
					{
						case DockType.left:
							//Give as much width as possible
							if (widthPixels > widthLeft)
							{
								widthPixels = widthLeft;
							}	
							//Take as much width as requested.
							item.item.width = widthPixels;
							//Take all the vertical space
							item.item.height = heightLeft;
							//Put it in the right place
							item.item.x = left;
							item.item.y = top;
							//Add to render list
							this.addChild(item.item);
							//Deduct from available.
							left += widthPixels;
						break;
						case DockType.right:
							//Give as much width as possible
							if (widthPixels > widthLeft)
							{
								widthPixels = widthLeft;
							}	
							//Take as much width as requested.
							item.item.width = widthPixels;
							//Take all the vertical space
							item.item.height = heightLeft;
							//Put it in the right place
							item.item.x = right - widthPixels;
							item.item.y = top;
							//Add to render list
							this.addChild(item.item);
							//Deduct from available.
							right -= widthPixels;
						break;
						case DockType.top:
							//Give as much height as possible
							if (heightPixels > heightLeft)
							{
								heightPixels = heightLeft;
							}	
							//Take as much height as requested.
							item.item.height = heightPixels;
							//Take all the horizontal space
							item.item.width = widthLeft;
							//Put it in the right place
							item.item.x = left;
							item.item.y = top;
							//Add to render list
							this.addChild(item.item);
							//Deduct from available.
							top += heightPixels;
						break;
						case DockType.bottom:
							//Give as much height as possible
							if (heightPixels > heightLeft)
							{
								heightPixels = heightLeft;
							}	
							//Take as much height as requested.
							item.item.height = heightPixels;
							//Take all the horizontal space
							item.item.width = widthLeft;
							//Put it in the right place
							item.item.x = left;
							item.item.y = bottom - heightPixels;
							//Add to render list
							this.addChild(item.item);
							//Deduct from available.
							bottom -= heightPixels;
						break;
						case DockType.fill: //Take the rest of the space.
							item.item.x = left;
							item.item.y = top;
							item.item.width = widthLeft;
							item.item.height = heightLeft;
							left += widthLeft;
							top += heightLeft;
							this.addChild(item.item);
						break;
					}
				}
				else //No room left, we're done.
				{
					break;					
				}
			}
		}
	}
}
import com.societyGames.flashForms.DockType;
import com.societyGames.flashForms.DockUnitType;

import flash.display.DisplayObject;

class DockItem
{
	private var _item:DisplayObject;
	private var _dockType:DockType;
	private var _dockUnitType:DockUnitType;
	private var _units:Number
	
	public function DockItem(item:DisplayObject, dockType:DockType, dockUnitType:DockUnitType, units:Number)
	{
		this._item = item;
		this._dockType = dockType;
		this._dockUnitType = dockUnitType;
		this._units = units;
	}
	
	public function get item():DisplayObject
	{
		return this._item;
	}
	
	public function get dockType():DockType
	{
		return this._dockType;
	}
	
	public function get dockUnitType():DockUnitType
	{
		return this._dockUnitType;
	}
	
	public function get units():Number
	{
		return this._units;
	}
}